<template>
  <!--ref="el"  相当于获得当前的dom元素-->
  <div class="slider" ref="slider">
    <div class="slider-group" ref="sliderGroup">
      <!--插槽 将写在组件中的内容放在插槽中-->
      <slot></slot>
    </div>
    <div class="dots">
      <span class="dot" v-for="(item,index) in dots" :class="{active: currentPageIndex === index}"></span>
    </div>
  </div>
</template>

<script type="text/ecmascript-6">
  // 引入BScroll实现轮播
  import BScroll from 'better-scroll'
  // 引进添加class方法
  import {addClass} from '../../common/js/dom'

  export default {
    // 设置需要用到的数据
    data() {
      return {
        dots: [],
        currentPageIndex: 0
      }
    },
    // 接收参数
    props: {
      loop: {// 是否循环轮播
        type: Boolean,
        default: true
      },
      antoPlay: {// 是否自动轮播
        type: Boolean,
        default: true
      },
      interval: {// 设置轮播间隔时间
        type: Number,
        default: 3000
      }
    },
    // 通常是初始化页面完成后，再对html的dom节点进行一些需要的操作。
    // 但不能保证钩子函数中的 this.$el 在 document 中。
    mounted() {
      // 保证dom渲染，此处使用延时(比this.$nextTick(fun)更加推荐使用)
      setTimeout(() => {
        // 设置slider宽度
        this._setSliderWidth()
        //  添加底部引导圆圈
        this._initDots()
        // 初始化slider中的 BScroll
        this._initSlider()
        if (this.antoPlay) {
          this._paly()
        }
        // 适应不同视口
        window.addEventListener('resize', () => {
          if (!this.slider) {
            return
          }
          this._setSliderWidth(true)
          // 重新计算
          this.slider.refresh()
        })
      }, 20)
    },
    methods: {
    //  横向滚动需要设置slider 的宽度
      _setSliderWidth(isResize) {
        this.children = this.$refs.sliderGroup.children
        let width = 0
        // slider的宽度等于设备的宽度
        let sliderWidth = this.$refs.slider.clientWidth
        for (let i = 0; i < this.children.length; i++) {
          let child = this.children[i]
          // 给每一个子元素添加slider-item （该方法意为：当前子元素有slider-item ，就不添加，没有就添加）
          addClass(child, 'slider-item')
          child.style.width = sliderWidth + 'px'
          width += sliderWidth
        }
        // 如果（this.loop为true 的话 会克隆两个dom 左右一个）
        if (this.loop && !isResize) {
          width += 2 * sliderWidth
        }
        this.$refs.sliderGroup.style.width = width + 'px'
      },
      // 初始化slider
      _initSlider() {
        this.slider = new BScroll(this.$refs.slider, {
          // 横向滚动
          scrollX: true,
          // 纵向不允许滚动
          scrollY: false,
          // 滚动的惯性
          momentum: false,
          // loop 为 true 是为了支持循环轮播，但只有一个元素的时候，loop 为 true 是无效的，
          snap: true,
          // 是否支持循环轮播
          snapLoop: this.loop,
          // 表示可滚动到下一个的阈值
          snapThreshold: 0.3,
          // 滚动的速度
          snapSpeed: 400
        })
        // 绑定一个事件记录currentPageIndex
        this.slider.on('scrollEnd', () => {
          // 返回值：{Object} { x: posX, y: posY,pageX: x, pageY: y}
          // 其中，x 和 y 表示偏移的坐标值，pageX 和 pageY 表示横轴方向和纵轴方向的页面数。
          let pageIndex = this.slider.getCurrentPage().pageX
          if (this.loop) {
            pageIndex -= 1
          }
          this.currentPageIndex = pageIndex

          if (this.antoPlay) {
            clearTimeout(this.timer)
            this._paly()
          }
        })
      },
      // 初始化dos(引导圆圈)
      _initDots() {
        // 长度为5的空数组
        this.dots = new Array(this.children.length)
      },
      // 自动播放
      _paly() {
        let pageIndex = this.currentPageIndex + 1
        if (this.loop) {
          pageIndex += 1
        }
        // 设置定时器
        this.timer = setInterval(() => {
          this.slider.goToPage(pageIndex, 0, 400)
        }, this.interval)
      }
    },
    destroyed() {
      clearTimeout(this.timer)
    }
  }
</script>

<style scoped lang="stylus" rel="stylesheet/stylus">
  @import "~common/stylus/variable"

  .slider
    min-height: 1px
    .slider-group
      position: relative
      overflow: hidden
      white-space: nowrap
      .slider-item
        float: left
        box-sizing: border-box
        overflow: hidden
        text-align: center
        a
          display: block
          width: 100%
          overflow: hidden
          text-decoration: none
        img
          display: block
          width: 100%
    .dots
      position: absolute
      right: 0
      left: 0
      bottom: 12px
      text-align: center
      font-size: 0
      .dot
        display: inline-block
        margin: 0 4px
        width: 8px
        height: 8px
        border-radius: 50%
        background: $color-text-l
        &.active
          width: 20px
          border-radius: 5px
          background: $color-text-ll
</style>
